package com.wisewin.pose.dao;

import com.wisewin.pose.entity.db.UserDO;
import com.wisewin.pose.entity.db.UserOrgAuthorizationDO;
import org.apache.ibatis.annotations.*;

import java.util.List;
import java.util.Map;

/**
 * DAO for accessing the tb_user_org_authorization table.
 */
@Mapper
public interface UserOrgAuthorizationDAO {

        static final String conditons = "<where> <if test='userName != null and userName != \"\"'> AND user_name LIKE CONCAT('%', #{userName}, '%')</if> <if test='sex != null'> AND sex = #{sex}</if> <if test='startTime != null'> AND DATE(create_time) &gt;= #{startTime}</if> <if test='endTime != null'> AND DATE(create_time) &lt;= #{endTime}</if> <if test='orgId != null and orgId != \"\"'> AND uoa.org_id = #{orgId} </if> AND uoa.deleted_at IS NULL </where> ORDER BY create_time DESC LIMIT #{pageOffset}, #{pageSize}";

        /**
         * Inserts a new record into the tb_user_org_authorization table.
         *
         * @param userOrgAuthorization the UserOrgAuthorizationDO object containing the
         *                             data to be inserted.
         * @return the number of rows affected.
         */
        @Insert("INSERT IGNORE INTO tb_user_org_authorization (openid, org_id) VALUES (#{openid}, #{orgId})")
        int insertOrIgnore(@Param("openid") String openid, @Param("orgId") int orgId);

        /**
         * Updates an existing record in the tb_user_org_authorization table.
         *
         * @param userOrgAuthorization the UserOrgAuthorizationDO object containing the
         *                             data to be updated.
         * @return the number of rows affected.
         */
        @Update("UPDATE tb_user_org_authorization SET device_id = #{deviceId}, authorization_date = #{authorizationDate}, "
                        +
                        "updated_at = #{updatedAt}, deleted_at = #{deletedAt} WHERE openid = #{openid} AND org_id = #{orgId}")
        int update(UserOrgAuthorizationDO userOrgAuthorization);

        /**
         * Deletes a record from the tb_user_org_authorization table.
         *
         * @param openid the openid of the user.
         * @param orgId  the id of the organization.
         * @return the number of rows affected.
         */
        @Delete("DELETE FROM tb_user_org_authorization WHERE openid = #{openid} AND org_id = #{orgId}")
        int delete(@Param("openid") String openid, @Param("orgId") int orgId);

        /**
         * Retrieves a record from the tb_user_org_authorization table by openid and
         * orgId.
         *
         * @param openid the openid of the user.
         * @param orgId  the id of the organization.
         * @return the UserOrgAuthorizationDO object containing the data.
         */
        @Select("SELECT * FROM tb_user_org_authorization WHERE openid = #{openid} AND org_id = #{orgId}")
        UserOrgAuthorizationDO selectByOpenidAndOrgId(@Param("openid") String openid, @Param("orgId") int orgId);

        /**
         * Retrieves all records from the tb_user_org_authorization table.
         *
         * @return a list of UserOrgAuthorizationDO objects containing the data.
         */
        @Select("SELECT * FROM tb_user_org_authorization")
        List<UserOrgAuthorizationDO> selectAll();

        static final String user_sql = "SELECT u.id, u.openid, u.user_name, u.sex, u.birthday, u.create_time, uoa.org_id FROM tb_user u JOIN tb_user_org_authorization uoa ON u.openid = uoa.openid ";

        /**
         * Retrieves user details for users associated with a specific organization ID.
         *
         * @param orgId the id of the organization.
         * @return a list of UserDO objects containing the user data.
         */
        @Select("<script>" + user_sql + conditons + "</script>")
        List<UserDO> selectAuthoredUsersByOrgId(Map<String, Object> map);

        static final String count_sql = "SELECT COUNT(*) FROM tb_user u JOIN tb_user_org_authorization uoa ON u.openid = uoa.openid ";

        /**
         * Counts the number of users matching the filtering conditions.
         *
         * @param map the map containing the filtering conditions.
         * @return the count of users.
         */
        @Select("<script>" + count_sql + conditons + " </script>")
        int queryAuthoredUserCount(Map<String, Object> map);
}